/*
 * Copyright (c) 2025 Industrial Software Feature Database
 */
package com.comac.ins.isfd.service.impl;

import cn.hutool.core.util.ObjectUtil;
import cn.hutool.json.JSONUtil;
import com.anwen.mongo.service.impl.ServiceImpl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.comac.ins.common.biz.aspectj.DigestAspect;
import com.comac.ins.common.core.domain.model.LoginUser;
import com.comac.ins.common.core.exception.base.BaseException;
import com.comac.ins.common.core.utils.MapstructUtils;
import com.comac.ins.common.json.utils.JsonUtils;
import com.comac.ins.common.satoken.utils.LoginHelper;
import com.comac.ins.isfd.domain.IsfdDatabaseModelingTemplate;
import com.comac.ins.isfd.domain.bo.IsfdDatabaseModelingTemplateBo;
import com.comac.ins.isfd.domain.bo.query.IsfdDatabaseModelingTemplateQueryBo;
import com.comac.ins.isfd.domain.vo.IsfdDatabaseModelConfigShowVo;
import com.comac.ins.isfd.domain.vo.IsfdDatabaseModelConfigVo;
import com.comac.ins.isfd.domain.vo.IsfdDatabaseModelingTemplateVo;
import com.comac.ins.isfd.domain.vo.IsfdDatabaseTypeManagementVo;
import com.comac.ins.isfd.mapper.IsfdDatabaseModelingTemplateMapper;
import com.comac.ins.isfd.service.IIsfdDatabaseModelConfigService;
import com.comac.ins.isfd.service.IIsfdDatabaseModelingTemplateService;
import com.comac.ins.isfd.service.IIsfdDatabaseTypeManagementService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.ByteArrayResource;
import org.springframework.core.io.Resource;
import org.springframework.stereotype.Service;

import java.nio.charset.StandardCharsets;
import java.util.*;


/**
 * 数据库模型模版管理Service业务层处理
 *
 * @author wujialin
 * @date 2024-12-05
 */
@RequiredArgsConstructor
@Service
@Slf4j
public class IsfdDatabaseModelingTemplateServiceImpl extends ServiceImpl<IsfdDatabaseModelingTemplate> implements IIsfdDatabaseModelingTemplateService {
    private static final Logger logger = LoggerFactory.getLogger(DigestAspect.class);
    @Autowired
    private final IsfdDatabaseModelingTemplateMapper baseMapper;

    @Autowired
    private final IIsfdDatabaseModelConfigService isfdDatabaseModelConfigService;

    @Autowired
    private final IIsfdDatabaseTypeManagementService isfdDatabaseTypeManagementService;

    @Override
    public List<IsfdDatabaseModelingTemplateVo> queryList(IsfdDatabaseModelingTemplateQueryBo bo) {
        List<IsfdDatabaseModelingTemplate> templateList = baseMapper.queryTemplateWithConfig(bo);
        List<IsfdDatabaseModelingTemplateVo> resultList = new LinkedList<>();
        for (IsfdDatabaseModelingTemplate isfdDatabaseModelingTemplate : templateList) {
            IsfdDatabaseModelingTemplateVo isfdDatabaseModelingTemplateVo = new IsfdDatabaseModelingTemplateVo();
            BeanUtils.copyProperties(isfdDatabaseModelingTemplate, isfdDatabaseModelingTemplateVo);
            if (Objects.nonNull(isfdDatabaseModelingTemplateVo) && Objects.nonNull(isfdDatabaseModelingTemplateVo.getDatabaseType())) {
                //要素库类型
                IsfdDatabaseTypeManagementVo isfdDatabaseTypeManagementVo = isfdDatabaseTypeManagementService.queryById(Long.parseLong(isfdDatabaseModelingTemplateVo.getDatabaseType()));
                if (Objects.nonNull(isfdDatabaseTypeManagementVo)) {
                    String databaseName = isfdDatabaseTypeManagementVo.getDatabaseName();
                    String parentDatabaseName = isfdDatabaseTypeManagementVo.getParentDatabaseName();
                    List<String> parts = new LinkedList<>();
                    if (StringUtils.isNotEmpty(parentDatabaseName)) {
                        parts.add(parentDatabaseName);
                    }
                    if (StringUtils.isNotEmpty(databaseName)) {
                        parts.add(databaseName);
                    }
                    String databaseTypeName = String.join("/", parts);

                    isfdDatabaseModelingTemplateVo.setDatabaseTypeName(databaseTypeName);
                }
                //模型
                Long configId = isfdDatabaseModelingTemplateVo.getConfigId();
                IsfdDatabaseModelConfigVo configVo = isfdDatabaseModelConfigService.queryByIdReturnSimpleVo(configId);
                if(Objects.nonNull(configVo)){
                    isfdDatabaseModelingTemplateVo.setIsfdDatabaseModelConfigVo(configVo);
                    isfdDatabaseModelingTemplateVo.setConfigName(configVo.getModelName());
                }
            }
            resultList.add(isfdDatabaseModelingTemplateVo);
        }
        return resultList;
    }

    @Override
    public IsfdDatabaseModelingTemplateVo queryById(Long id) {
        IsfdDatabaseModelingTemplateVo isfdDatabaseModelingTemplateVo = baseMapper.selectVoById(id);
        if (!Objects.nonNull(isfdDatabaseModelingTemplateVo)) {
            throw new BaseException("找不到模版数据！");
        }
        //要素库类型
        IsfdDatabaseTypeManagementVo isfdDatabaseTypeManagementVo = isfdDatabaseTypeManagementService.queryById(Long.parseLong(isfdDatabaseModelingTemplateVo.getDatabaseType()));
        if (Objects.nonNull(isfdDatabaseTypeManagementVo)) {
            String databaseName = isfdDatabaseTypeManagementVo.getDatabaseName();
            String parentDatabaseName = isfdDatabaseTypeManagementVo.getParentDatabaseName();
            List<String> parts = new LinkedList<>();
            if (StringUtils.isNotEmpty(parentDatabaseName)) {
                parts.add(parentDatabaseName);
            }
            if (StringUtils.isNotEmpty(databaseName)) {
                parts.add(databaseName);
            }
            String databaseTypeName = String.join("/", parts);
            isfdDatabaseModelingTemplateVo.setDatabaseTypeName(databaseTypeName);
        }
        //模型
        Long configId = isfdDatabaseModelingTemplateVo.getConfigId();
        IsfdDatabaseModelConfigVo configVo = isfdDatabaseModelConfigService.queryByIdReturnSimpleVo(configId);
        Map<String, Object> templateMap = isfdDatabaseModelConfigService.getTemplate(configId);
        if(Objects.nonNull(configVo)){
            isfdDatabaseModelingTemplateVo.setIsfdDatabaseModelConfigVo(configVo);
            isfdDatabaseModelingTemplateVo.setConfigName(configVo.getModelName());
        }
        isfdDatabaseModelingTemplateVo.setTemplateMapString(JsonUtils.toJsonString(templateMap));
        return isfdDatabaseModelingTemplateVo;
    }

    @Override
    public Boolean save(IsfdDatabaseModelingTemplateBo bo) {
        IsfdDatabaseModelingTemplate save = MapstructUtils.convert(bo, IsfdDatabaseModelingTemplate.class);
        LoginUser loginUser = LoginHelper.getLoginUser();
        save.setUpdateBy(loginUser.getUserId());
        save.setIsDelete(0);
        Date current = ObjectUtil.isNotNull(bo.getCreateTime())
            ? bo.getCreateTime() : new Date();
        save.setUpdateTime(current);
        boolean flag;
        // 判断新增还是修改
        Long id = bo.getId();
        if (Objects.isNull(id)) {
            //新增
            save.setCreateBy(loginUser.getUserId());
            save.setCreateTime(current);
            flag = baseMapper.insert(save) > 0;
        } else {
            //修改
            flag = baseMapper.updateById(save) > 0;
        }
        return flag;
    }

    private LambdaQueryWrapper<IsfdDatabaseModelingTemplate> buildQueryWrapper(IsfdDatabaseModelingTemplateBo bo) {
        LambdaQueryWrapper<IsfdDatabaseModelingTemplate> lqw = Wrappers.lambdaQuery();
        lqw.like(StringUtils.isNotBlank(bo.getTemplateName()), IsfdDatabaseModelingTemplate::getTemplateName, bo.getTemplateName());
        lqw.like(StringUtils.isNotBlank(bo.getTemplateDescription()), IsfdDatabaseModelingTemplate::getTemplateDescription, bo.getTemplateDescription());
        lqw.eq(bo.getIsDelete() != null, IsfdDatabaseModelingTemplate::getIsDelete, bo.getIsDelete());
        return lqw;
    }

    @Override
    public Boolean deleteWithValidById(Long id, Boolean isValid) {
        boolean flag;
        IsfdDatabaseModelingTemplate isfdDatabaseModelingTemplate = baseMapper.selectById(id);
        isfdDatabaseModelingTemplate.setIsDelete(1);
        flag = baseMapper.updateById(isfdDatabaseModelingTemplate) > 0;
        return flag;
    }

    @Override
    public Resource outJson(IsfdDatabaseModelingTemplateVo isfdDatabaseModelingTemplateVo) {
        Map<String, Object> templateMap = isfdDatabaseModelConfigService.getTemplate(isfdDatabaseModelingTemplateVo.getConfigId());
        // 将result包装到列表中，生成JSON数组
        List<Map<String, Object>> resultList = Collections.singletonList(templateMap);
        return new ByteArrayResource(JSONUtil.parse(resultList).toStringPretty().getBytes(StandardCharsets.UTF_8));
    }
//
//    @Override
//    public Integer importExcelToMongo(MultipartFile file, String templateId) {
//        try (InputStream inputStream = file.getInputStream()) {
//            IsfdDatabaseModelingTemplateVo isfdDatabaseModelingTemplateVo = baseMapper.selectVoById(templateId);
//            IsfdDatabaseModelingConfig isfdDatabaseModelingConfig = databaseModelingConfigMapper.selectById(isfdDatabaseModelingTemplateVo.getConfigId());
//            List<Map<String, String>> converted = new LinkedList<>();
//            List<Map<Integer, String>> excelData = new LinkedList<>();
//            if (Objects.nonNull(isfdDatabaseModelingConfig)) {
//                String tableName = isfdDatabaseModelingConfig.getTableName();
//                if (!StringUtils.isEmpty(tableName)) {
//                    excelData = EasyExcel.read(inputStream)
//                        .headRowNumber(0)
//                        .sheet(0)
//                        .doReadSync();
//                    Map<Integer, String> header = excelData.get(0);
//                    List<IsfdDatabaseModelingTemplateConfigVo> databaseModelingTemplateConfigAllList = databaseModelingTemplateConfigMapper.queryDatabaseModelingTemplateConfigByTemplateId(Long.getLong(templateId));
//                    Set<String> allFieldNames = databaseModelingTemplateConfigAllList.stream()
//                        .map(IsfdDatabaseModelingTemplateConfigVo::getFieldName)
//                        .collect(Collectors.toSet());
//
//                    Set<String> headerFieldNames = new HashSet<>(header.values());
//                    for (String headerFieldName : headerFieldNames) {
//                        if (!allFieldNames.contains(headerFieldName)) {
//                            throw new BaseException("fieldName 不存在" + headerFieldName + "请确认");
//                        }
//                    }
//
//
//                    for (int i = 1; i < excelData.size(); i++) {
//                        Map<Integer, String> rowData = excelData.get(i);
//                        Map<String, String> convertedData = new HashMap<>();
//                        for (int j = 0; j < rowData.size(); j++) {
//                            convertedData.put(header.get(j), rowData.get(j));
//                        }
//                        converted.add(convertedData);
//                    }
//                }
//
//                MongoDatabase database = mongoClient.getDatabase(DB_NAME);
//                MongoIterable<String> collectionNameList = database.listCollectionNames();
//
//                Boolean flag = false;
//                for (String s : collectionNameList) {
//                    if (tableName.equals(s)) {
//                        flag = true;
//                        break;
//                    }
//                }
//                if (flag) {
//                    MongoCollection<Document> collection = database.getCollection(tableName);
//
//                    List<Document> documents = new ArrayList<>();
//                    for (Map<String, String> rowData : converted) {
//                        Document document = new Document();
//                        for (Map.Entry<String, String> entry : rowData.entrySet()) {
//                            document.append(entry.getKey(), entry.getValue());
//                        }
//                        documents.add(document);
//                    }
//
//                    collection.insertMany(documents);
//                } else {
//                    throw new BaseException("tableName 不存在");
//                }
//                return excelData.size() - 1;
//            }
//            return null;
//        } catch (Exception e) {
//            throw new BaseException("导入 Excel 到 MongoDB 失败");
//        }
//
//    }


}
